package com.gitee.helioz.openai.api.dto.finetune;

import com.google.gson.annotations.SerializedName;
import lombok.Data;

import java.util.List;

/**
 * 〈创建微调请求〉
 *
 * @author <a href="https://gitee.com/helioz">Morning Starr</a>
 */
@Data
public class FineTuneCreateRequest {

    /**
     * 已上传文件的ID
     * <pre>必填</pre>
     */
    @SerializedName("training_file")
    private String trainingFile;

    /**
     * 用于指定包含验证数据的已上传文件的 ID。这个文件可以用来在训练过程中对模型进行验证和评估。
     * <pre>选填</pre>
     */
    @SerializedName("validation_file")
    private String validationFile;

    /**
     * 默认值： curie，用于指定要进行 fine-tune 的基础模型的名称。
     * 可以选择以下其中之一的值："ada", "babbage", "curie", "davinci"，或者在 2022-04-21 之后创建的已 fine-tune 模型。
     * <pre>选填</pre>
     *
     * @see com.gitee.helioz.openai.api.dto.finetune.FineTuneModelEnum
     */
    private String model;

    /**
     * 默认值： 4，用于指定模型训练的轮数，也称为 epoch。每个 epoch 指的是一次完整的训练数据集循环。
     * <pre>选填</pre>
     */
    @SerializedName("n_epochs")
    private Integer nEpochs;

    /**
     * 用于指定模型训练时的批处理大小。批处理大小指的是在单次前向和反向传播过程中用于训练的训练样本数量。
     * 注意，默认情况下，批处理大小会根据训练集中的示例数量动态配置为约为训练集示例数量的 0.2%，并且最大值不超过 256，
     * 因为通常较大的批处理大小对于较大的数据集效果更好。
     * <pre>选填</pre>
     */
    @SerializedName("batch_size")
    private Integer batchSize;

    /**
     * 用于指定模型训练时的学习率倍数。细调学习率是预训练时使用的原始学习率乘以这个倍数值。
     * 注意，默认情况下，学习率倍数会根据批处理大小自动选择为 0.05、0.1 或 0.2，具体取决于最终的批处理大小，
     * 因为较大的学习率倍数通常在较大的批处理大小下效果更好。建议尝试在 0.02 到 0.2 的范围内的值，以找到产生最佳结果的学习率倍数值。
     * <pre>选填</pre>
     */
    @SerializedName("learning_rate_multiplier")
    private Double learningRateMultiplier;

    /**
     * 默认值： 0.01，用于控制模型在训练过程中对于 prompt tokens 的损失权重。
     * 通过调整这个权重，可以控制模型在学习生成提示（prompt）和生成完成（completion）时的权衡关系，从而对训练过程进行稳定调节。<pre>
     * 较大的 "prompt_loss_weight" 值会使模型在训练过程中更加关注生成提示的准确性，从而更加重视学习生成高质量的提示。
     * 这可能会导致模型在生成完成时更加忠实于提示，但生成的内容可能会受到限制，过于保守，缺乏创造性。
     * 较小的 "prompt_loss_weight" 值会使模型在训练过程中更加关注生成完成的内容，从而更加注重学习生成高质量的完成。
     * 这可能会导致模型在生成时更加自由、创造性，但可能会忽略提示的准确性，导致生成的内容与提示不一致。</pre>
     * <pre>选填</pre>
     */
    @SerializedName("prompt_loss_weight")
    private Double promptLossWeight;

    /**
     * 默认值： false，用于设定模型在训练过程中是否计算分类特定的度量指标，如准确性和 F1 分数，并在每个 epoch 结束时使用验证集进行评估。
     * 需要注意的是，为了计算分类指标，必须提供一个验证文件（validation_file），
     * 同时还需要指定分类的类别数（classification_n_classes）用于多类别分类，
     * 或者指定二分类中的正类别（classification_positive_class）用于二分类。
     * <pre>选填</pre>
     */
    @SerializedName("compute_classification_metrics")
    private Boolean computeClassificationMetrics;

    /**
     * 用于指定模型微调中的多类别分类任务中的类别数。当进行多类别分类任务时，需要设置这个参数，以告诉模型总共有多少个类别需要进行分类。
     * <pre>
     * 例如，如果你的任务是将文本分类到10个不同的类别中，那么你应该将 "classification_n_classes" 参数设置为 10。
     * 这个参数的设置对于模型的训练和性能评估非常重要，因为它影响了模型在多类别分类任务中的输出和预测。
     * 确保设置 "classification_n_classes" 参数的值与你的实际任务中的类别数相匹配，以确保模型能够正确地进行多类别分类。</pre>
     * <pre>选填</pre>
     */
    @SerializedName("classification_n_classes")
    private Integer classificationNClasses;

    /**
     * 用于指定模型微调中的二分类任务中的正类别。在进行二分类任务时，可以使用这个参数来指定哪个类别被认为是正类别。
     * <pre>
     * 例如，如果你的任务是进行情感分析，其中需要将文本分类为 "positive" 和 "negative" 两个类别，
     * 你可以使用 "classification_positive_class" 参数来指定 "positive" 类别作为正类别。
     * 这个参数的设置对于模型的训练和性能评估非常重要，因为它影响了模型在二分类任务中的输出和预测。
     * 确保设置 "classification_positive_class" 参数的值与你的实际任务中的正类别相匹配，以确保模型能够正确地进行二分类任务。</pre>
     * <pre>选填</pre>
     */
    @SerializedName("classification_positive_class")
    private String classificationPositiveClass;

    /**
     * 用于微调模型中的二分类任务中的样本权重调整。它是一个长度为2的浮点数列表，用于调整正类别和负类别的权重。
     * 这两个浮点数分别表示正类别和负类别的权重调整因子，可以用来平衡不同类别之间的样本数量不平衡。
     * 例如，如果正类别在训练数据中较为稀缺，可以通过增加正类别的权重调整因子来增加对正类别的关注度。
     * 默认情况下，"classification_betas" 参数的值为 [0.0, 0.0]，表示没有样本权重调整。
     * 如果需要在二分类任务中进行样本权重调整，可以设置 "classification_betas" 参数的值来实现类别平衡或样本重要性调整。
     * <pre>选填</pre>
     */
    @SerializedName("classification_betas")
    private List<Object> classificationBetas;

    /**
     * 后缀，用于设置一个最多40个字符的字符串，该字符串将被添加到您的微调模型名称后面。
     * <pre>
     * 例如，如果您设置了一个名为 "custom-model-name" 的后缀，
     * 那么生成的模型名称可能类似于 "ada:ft-your-org:custom-model-name-2022-02-15-04-21-04"，
     * 其中 "ada" 是基础模型名称，"ft-your-org" 是您的组织名称，"custom-model-name" 是您设置的后缀，
     * 而 "2022-02-15-04-21-04" 是生成模型的日期和时间戳。
     * 通过设置后缀，您可以为您的微调模型添加自定义标识，以便更好地管理和识别您的模型。</pre>
     * <pre>选填</pre>
     */
    private String suffix;

}
